<template>
  <div>
    <!-- 表单与分页器组件 -->
    <el-card class="box-card">
      <!-- 卡片顶部添加品牌的按钮 -->
      <el-button type="primary" icon="Plus" @click="addTrademark">
        添加品牌
      </el-button>
      <!-- 表格组件：用于展示已有的品牌数据 -->
      <!-- 
    table 
      --border：可以设置表格纵向是否有边框
    table-column
      --label：列名
      --width：宽度设置
      --align：对齐方式 
    -->
      <el-table style="margin: 10px 0" border :data="trademarkArr">
        <el-table-column
          label="序号"
          width="80px"
          align="center"
          type="index"
        ></el-table-column>
        <el-table-column label="品牌名称" align="center">
          <template #default="{ row }">
            <el-link type="primary" :underline="false">
              {{ row.tmName }}
            </el-link>
          </template>
        </el-table-column>
        <el-table-column label="品牌LOGO" align="center" prop="logoUrl">
          <template #default="{ row }">
            <el-image style="width: 100px; height: 100px" :src="row.logoUrl">
              <template #error>
                <div class="image-slot">
                  <img
                    src="@/assets/images/NAN.jpg"
                    alt=""
                    style="width: 100px; height: 100px"
                  />
                </div>
              </template>
            </el-image>
          </template>
        </el-table-column>
        <el-table-column label="品牌操作" align="center">
          <template #default="{ row }">
            <el-button
              type="primary"
              icon="Edit"
              circle
              @click="updateTrademark(row)"
            ></el-button>
            <el-popconfirm
              :title="`您确定要删除${row.tmName}吗?`"
              width="230px"
              icon="Delete"
              @confirm="removeTrademark(row.id)"
            >
              <template #reference>
                <el-button type="danger" icon="Delete" circle></el-button>
              </template>
            </el-popconfirm>
          </template>
        </el-table-column>
      </el-table>
      <!-- 分页器组件 -->
      <!-- 
      pagination
      --v-model:current-page：设置分页器当前页码
      --v-model:page-size：设置每一个展示数据条数
      --page-sizes：用于设置下拉菜单数据
      --background：用于设置分页器按钮背景颜色
      --layout：分页器子组件布局调整
      --total：用于设置分页器总条数
     -->
      <el-pagination
        v-model:current-page="pageNo"
        v-model:page-size="limit"
        :page-sizes="[3, 5, 7, 9]"
        background
        layout="prev, pager, next, jumper,-> ,sizes, total"
        :total="total"
        @size-change="handleSizeChange"
        @current-change="handleCurrentChange"
      />
    </el-card>
    <!-- 对话框组件：在添加品牌与修改已有品牌的业务的时候触发 -->
    <el-dialog
      v-model="dialogFormVisible"
      :title="trademarkParams.id ? '修改品牌' : '添加品牌'"
    >
      <el-form
        style="width: 80%"
        :model="trademarkParams"
        :rules="rules"
        ref="form"
      >
        <el-form-item label="品牌名称：" prop="tmName">
          <el-input
            placeholder="请输入品牌名称"
            size="large"
            class="trademarkName"
            v-model="trademarkParams.tmName"
          ></el-input>
        </el-form-item>
        <el-form-item label="品牌LOGO：" prop="logoUrl">
          <el-upload
            class="upload-demo"
            drag
            action="/api/admin/product/fileUpload"
            :show-file-list="false"
            :before-upload="beforeAvatarUpload"
            :on-success="handleAvatarSuccess"
          >
            <img
              v-if="trademarkParams.logoUrl"
              :src="trademarkParams.logoUrl"
              style="width: 200px; height: 200px"
            />
            <div v-if="!trademarkParams.logoUrl">
              <el-icon class="el-icon--upload"><upload-filled /></el-icon>
              <div class="el-upload__text">
                拖拽上传或
                <em>点击上传图片</em>
              </div>
            </div>
          </el-upload>
        </el-form-item>
      </el-form>
      <!-- 具名插槽：footer -->
      <template #footer>
        <el-button type="default" size="large" @click="cancel">取消</el-button>
        <el-button type="primary" size="large" @click="confirm">确定</el-button>
      </template>
    </el-dialog>
  </div>
</template>

<script setup lang="ts">
// 引入组合式API函数ref
import { ref, nextTick } from 'vue'
import {
  reqHasTrademark,
  reqAddorUpdateTrademark,
  reqDeleteTrademark,
} from '@/api/product/trademark'
import type {
  Records,
  TradeMark,
  TradeMarkResponseData,
} from '@/api/product/trademark/type'

// 当前页码
const pageNo = ref(1)
// 每一页展示多少条数据
const limit = ref(3)
// 存储已有品牌的数据总数
const total = ref(0)
// 存储已有品牌的数据
const trademarkArr = ref<Records>([])
// 控制对话框的显示和隐藏
const dialogFormVisible = ref(false)
// 定义收集新增品牌的数据
const trademarkParams = ref<TradeMark>({
  id: undefined,
  tmName: '',
  logoUrl: '',
})
// 获取form表单内容，后续进行表单验证
const form = ref()
// 表单校验规则
const rules = {
  tmName: [
    { required: true, message: '请输入品牌名称', trigger: 'blur' },
    { min: 2, message: '品牌名称大于等于两位', trigger: 'change' },
  ],
  logoUrl: [
    {
      required: true,
      // @ts-expect-error 避免rule报已使用未取值的错误
      validator: (rule: any, value: any, callBack: any) => {
        if (value) {
          callBack()
        } else {
          callBack(new Error('请上传品牌LOGO'))
        }
      },
    },
  ],
}

// 获取已有品牌的接口封装为一个函数：在任何情况下想获取数据，调用此函数即可
const getHasTrademark = async (pager = 1) => {
  pageNo.value = pager
  const res: TradeMarkResponseData = await reqHasTrademark(
    pageNo.value,
    limit.value,
  )
  if (res.code === 200) {
    // 存储已有品牌总个数
    total.value = res.data.total
    trademarkArr.value = res.data.records
  }
}
getHasTrademark()

// 当下拉菜单发生变化的时候触发的事件
const handleSizeChange = () => {
  // 当前每一页数据变化的时候，当前页码归1
  getHasTrademark()
}

// 分页器当前页面发生变化触发的事件
const handleCurrentChange = (num: number) => {
  // 当前页码发生变化的时候再次发送请求获取对应已有品牌的数据
  getHasTrademark(num)
}

// 添加品牌按钮的回调
const addTrademark = () => {
  // 清空校验规则错误提升信息
  nextTick(() => {
    form.value.clearValidate()
  })
  // 收集的数据清空
  trademarkParams.value.id = undefined
  trademarkParams.value.tmName = ''
  trademarkParams.value.logoUrl = ''
  // 对话框显示
  dialogFormVisible.value = true
}

// 修改已有品牌按钮的回调
const updateTrademark = (row: TradeMark) => {
  // 清空校验规则错误提升信息
  nextTick(() => {
    form.value.clearValidate()
  })
  // ES6语法复制对象，把row数据复制给trademarkParams
  Object.assign(trademarkParams.value, row)
  // 对话框显示
  dialogFormVisible.value = true
}

// 对话框底部取消按钮的回调
const cancel = () => {
  // 对话框隐藏
  dialogFormVisible.value = false
}

// 对话框底部确认按钮的回调
const confirm = async () => {
  await form.value.validate()
  const res = await reqAddorUpdateTrademark(trademarkParams.value)
  const msg = trademarkParams.value.id ? '修改' : '添加'
  // 添加/修改品牌成功
  if (res.code === 200) {
    // 弹出提示信息
    ElMessage.success(`${msg}品牌成功`)
    // 再次发送请求获取已有品牌的数据
    getHasTrademark(trademarkParams.value.id ? pageNo.value : 1)
  } else {
    // 添加/修改品牌失败
    ElMessage.error(`${msg}品牌失败`)
  }
  // 关闭对话框
  dialogFormVisible.value = false
}

// 上传图片组件 -> 上传图片之前触发的钩子函数
const beforeAvatarUpload = (rawFile: any) => {
  // 钩子是在图片上传成功之前触发的，上传文件之前可以约束文件类型和大小
  // 要求：上传文件格式是png|jpg|gif 4M
  if (
    rawFile.type === 'image/png' ||
    rawFile.type === 'image/jpeg' ||
    rawFile.type === 'image/gif'
  ) {
    if (rawFile.size / 1024 / 1024 < 4) {
      return true
    } else {
      ElMessage.error('上传图片大小不能超过 4M')
      return false
    }
  } else {
    ElMessage.error('上传文件格式务必为 PNG | JPG | GIF ')
    return false
  }
}

// 图片上传成功的钩子
const handleAvatarSuccess = (response: any) => {
  // response：即为当前这次上传图片post请求服务器返回的数据
  // 收集上传图片的地址，添加一个新的品牌的时候带给服务器
  trademarkParams.value.logoUrl = response.data
  // 图片上传成功，清除掉对应图片校验结果
  form.value.clearValidate('logoUrl')
}

// 气泡确认框确定按钮的回调
const removeTrademark = async (id: number) => {
  const res = await reqDeleteTrademark(id)
  if (res.code === 200) {
    ElMessage.success('删除品牌成功')
    getHasTrademark(
      trademarkArr.value.length > 1 ? pageNo.value : pageNo.value - 1,
    )
  } else {
    ElMessage.error('删除品牌失败')
  }
}
</script>

<style lang="scss" scoped>
:deep() {
  .el-upload-dragger {
    width: 200px;
    height: 200px;
    display: grid;
    justify-content: center;
    align-content: center;
  }
  .el-form-item__error {
    font-size: 13px;
  }
  .el-input ~ .el-form-item__error {
    margin-left: 10.5px;
  }
}
.trademarkName {
  margin-left: 10.5px;
}
</style>
